#include <iostream>

/*
1. 引用&指针
引用是一种更安全的指针
引用是必须初始化的，指针可以不初始化
引用只有一级引用，没有多级引用，不是对象没有内存空间，无法重新绑定赋值，一旦创建绑定，则无法更改，访问引用即是访问所绑定对象
指针可以有多级指针，是一个对象，有自己的内存空间
定义一个引用和定义一个指针，其汇编指令一模一样
通过引用修改引用内存的值和通过指针解引用修改指针所指内存的值
其汇编指令也是一模一样的

定义一个数组的引用
int arr[5] = {};
int (&ref)[5] = arr;

*/

#if 0
void swap(int *x, int *y) {
  int tmp = *x;
  *x = *y;
  *y = tmp;
}

void swap(int &x, int &y) {
  int tmp = x;
  x = y;
  y = tmp;
}

int main() {
  int a = 10;
  int *p = &a; // 指针可以不初始化
  int &r = a;  // 引用必须初始化
  // int &r2;   // Declaration of reference variable 'r2' requires an
  // initializer

  *p = 20;
  std::cout << a << " " << *p << " " << r << std::endl; // 20 20 20

  r = 30;
  std::cout << a << " " << *p << " " << r << std::endl; // 30 30 30

  int m = 1, n = 2;
  swap(&m, &n);
  std::cout << m << " " << n << std::endl;
  swap(m, n);
  std::cout << m << " " << n << std::endl;
}
#endif

/*
2. 左值引用和右值引用
左值， 有内存，有名字，值可以修改
右值， 没有内存，没名字，
int &&ref = 20; 使用右值引用引用右值，指令上，可以自动产生临时量，然后引用临时量
右值引用变量本身是一个左值，


*/

int main() {
  int a = 10; //a是左值， 10是右值
  int &refa = a;  

  // int *referror = 20;
  int &&reftmp = 20;  // 右值引用

   
}